﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using MarvinsArena.Core;

namespace BattleLogic
{
	class LogicCollision
	{
		private bool CheckForCollisions(IWorldObject obj1, IWorldObject obj2)
		{
			double xdif = obj1.PositionX - obj2.PositionX;
			double ydif = obj1.PositionY - obj2.PositionY;

			double distance = Math.Sqrt(xdif * xdif + ydif * ydif);

			if (distance <= obj1.Radius + obj2.Radius)
				return true;

			return false;
		}

		public List<string> Check(List<Robot> robots, Map map, List<IProjectile> projectiles)
		{
			List<string> hudMessages = new List<string>();

			foreach (IRobot robot in robots)
			{
				// Collision: robot vs Walls
                if (map.CheckCollision(robot))
                {
                    ((Robot)robot).NotifyCollision(
                        new MarvinsArena.Robot.Core.Collision("Wall", 1,
                            MarvinsArena.Robot.Core.MessageExchangeType.Wall)
                        );
                    hudMessages.Add(string.Format(Resourses.Hud.CollisionRobotWall, robot.FullName));
                }

				// Collision: robot vs robot and SCAN
				foreach (IRobot robot2 in robots)
				{
					if (robot == robot2)
						continue;

					if (this.CheckForCollisions(robot, robot2))
					{
						((Robot)robot).NotifyCollision(
							new MarvinsArena.Robot.Core.Collision(
								robot2.FullName, 1,
								MarvinsArena.Robot.Core.MessageExchangeType.Robot)
							);

						hudMessages.Add(String.Format(Resourses.Hud.CollisionRobotRobot, robot.FullName, robot2.FullName));
					}

					if (((Robot)robot).TargetInScannerRange(robot2))
					{
						((Robot)robot).NotifyTarget(
							new MarvinsArena.Robot.Core.ScannerTarget(
								robot2.PositionX, robot2.PositionY, robot2.FullName,
								MarvinsArena.Robot.Core.MessageExchangeType.Robot)
							);
					}
				}

				// Collision: robot vs Projectile
				foreach (IProjectile projectile in projectiles)
				{
					if (this.CheckForCollisions(robot, projectile) && !((ILogicObject)projectile).Dead)
					{
						MarvinsArena.Robot.Core.MessageExchangeType typeProjectile;

						if (projectile.TypeWorldObject == TypeWorldObjects.Missile)
							typeProjectile = MarvinsArena.Robot.Core.MessageExchangeType.Missile;
						else
							typeProjectile = MarvinsArena.Robot.Core.MessageExchangeType.Bullet;

						((Robot)robot).NotifyCollision(
							new MarvinsArena.Robot.Core.Collision(
								projectile.Name,
								projectile.Power,
								typeProjectile)
						);

						((ILogicObject)projectile).Dead = true;

						hudMessages.Add(string.Format(Resourses.Hud.CollisionRobotProjectile, robot.FullName,
							projectile.Name, projectile.Power));
					}
				}
			}

			foreach (IProjectile projectile in projectiles)
			{
				// Collision: Projectile vs Walls
				if(map.CheckCollision(projectile))
					((ILogicObject)projectile).Dead = true;

				// Collision: Projectile vs Projectile
				foreach (IProjectile projectile2 in projectiles)
				{
					if (projectile == projectile2 || ((ILogicObject)projectile).Dead || ((ILogicObject)projectile2).Dead)
						continue;

					if (this.CheckForCollisions(projectile, projectile2))
					{
						((ILogicObject)projectile).Dead = true;
						((ILogicObject)projectile2).Dead = true;
					}
				}
			}

			return hudMessages;
		}
	}
}
